package com.cn.sl.server.util

import com.fasterxml.jackson.databind.DeserializationFeature
import com.fasterxml.jackson.databind.ObjectMapper
import com.fasterxml.jackson.databind.module.SimpleModule
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer
import com.fasterxml.jackson.databind.type.CollectionType
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateDeserializer
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateTimeDeserializer
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer
import com.fasterxml.jackson.module.kotlin.KotlinModule
import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
import java.math.BigInteger
import java.time.LocalDate
import java.time.LocalDateTime
import java.time.format.DateTimeFormatter

val objectMapper: ObjectMapper
    get() {
        return initObjectMapper()
    }

fun <T> parseList(json: String, clz: Class<T>): List<T> {
    val javaType: CollectionType = objectMapper.typeFactory.constructCollectionType(MutableList::class.java, clz)
    return objectMapper.readValue(json, javaType)
}

fun toJsonStr(obj: Any): String {
    return objectMapper.writeValueAsString(obj)
}

private fun initObjectMapper(): ObjectMapper {
    val simpleModule = SimpleModule()
    simpleModule.addSerializer(BigInteger::class.java, ToStringSerializer.instance)
    simpleModule.addSerializer(Long::class.javaPrimitiveType, ToStringSerializer.instance)
    simpleModule.addSerializer(Long::class.javaObjectType, ToStringSerializer.instance)

    simpleModule.addSerializer(
        LocalDateTime::class.java,
        LocalDateTimeSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"))
    )
    simpleModule.addSerializer(
        LocalDate::class.java,
        LocalDateSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd"))
    )

    simpleModule.addDeserializer(
        LocalDateTime::class.java,
        LocalDateTimeDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"))
    )
    simpleModule.addDeserializer(
        LocalDate::class.java,
        LocalDateDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd"))
    )


    val objectMapper = jacksonObjectMapper()
    // 忽略前端多传的字段
    objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false)
    objectMapper.registerModule(simpleModule)
    objectMapper.registerModule(KotlinModule.Builder().build())
    return objectMapper
}